package club.jdiy.dev.zlt.controller;

import club.jdiy.admin.interceptor.GuestDisabled;
import club.jdiy.core.base.JDiyCtrl;
import club.jdiy.core.base.domain.Pager;
import club.jdiy.core.base.domain.Ret;
import club.jdiy.core.sql.ColumnInfo;
import club.jdiy.core.sql.EntityInfo;
import club.jdiy.core.sql.EntityFieldInfo;
import club.jdiy.dev.controller.JDiyController;
import club.jdiy.dev.entity.JDiyUi;
import club.jdiy.dev.service.JDiyUiService;
import club.jdiy.utils.StringUtils;
import org.springframework.stereotype.Controller;
import org.springframework.ui.ModelMap;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.ResponseBody;

import java.util.List;
import java.util.stream.Collectors;

@Controller("JDiy_EntityCtrl")
@RequestMapping("mgmt/JDiyAdmin")
public class EntitiesCtrl extends JDiyCtrl<JDiyUi, JDiyUiService> implements JDiyController {

    @GetMapping(value = "entity.list")
    public String ls(ModelMap map, String packageName, String key) {
        List<EntityInfo> ls = context.getDao().getEntityMeta()
                .stream().filter(o -> {
                    boolean b = StringUtils.isEmpty(packageName) || o.getPackageName().equals(packageName);
                    if (b && StringUtils.hasText(key))
                        b = o.getName().contains(key)
                                || o.getTableName() != null && o.getTableName().contains(key)
                                || o.getComment() != null && o.getComment().contains(key);
                    return b;
                }).collect(Collectors.toList());
        map.put("pager", new Pager<>(1, ls.size(), ls.size(), ls));
        map.put("packageName", packageName);
        map.put("key", key);
        return "entity.ls";
    }

    @GetMapping(value = "entity.fields")
    public String fields(ModelMap map, String name, String key) {
        EntityInfo entityInfo = context.getDao().getEntityMeta(name);
        List<EntityFieldInfo> ls = entityInfo.getFieldList();
        if (StringUtils.hasText(key)) {
            String k = key.trim();
            ls = ls.stream()
                    .filter(o -> o.getName().contains(k)
                            || o.getColumn() != null && o.getColumn().contains(k)
                            || o.getComment() != null && o.getComment().contains(k)
                    ).collect(Collectors.toList());
        }
        map.put("key", key);
        map.put("entity", entityInfo);
        map.put("pager", new Pager<>(1, ls.size(), ls.size(), ls));
        return "entity.field.ls";
    }

    @GuestDisabled
    @ResponseBody
    @RequestMapping(value = "entity.updateTableComment")
    public Ret<String> updateTableComment(String tableName, String comment) {
        try {
            context.getDao().exec("alter table " + tableName + " comment ?", comment);
            return Ret.success();
        } catch (Exception ex) {
            return Ret.error(ex);
        }
    }

    @GuestDisabled
    @ResponseBody
    @RequestMapping(value = "entity.updateColumnComment")
    public Ret<String> updateColumnComment(String tableName, String columnName, String comment) {
        try {
            ColumnInfo colMeta = context.getDao().getColumns(tableName).get(columnName);
            if (colMeta != null) {
                String def = colMeta.getDefaultValue();
                String ddl = "ALTER TABLE " + tableName + " MODIFY COLUMN " + columnName + " " + colMeta.getType()
                        + (def != null && !"NULL".equals(def) ? " default " + def : "")
                        + (
                        "auto_increment".equals(colMeta.getExtra())
                                ? " auto_increment "
                                : (colMeta.isNullable() ? " null" : " not null"))
                        + " comment '" + comment.replaceAll("'", "''") + "'";
                context.getDao().exec(ddl);
                context.getCacheClient().delete("JDiyTableColumnsMetaInfo_" + tableName);
            }
            return Ret.success();
        } catch (Exception ex) {
            return Ret.error(ex);
        }
    }

}
